package cn.seaboot.admin.mvc.utils;

import org.springframework.expression.EvaluationContext;
import org.springframework.expression.Expression;
import org.springframework.expression.ExpressionParser;
import org.springframework.expression.common.TemplateParserContext;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.expression.spel.support.StandardEvaluationContext;

import javax.annotation.Nullable;
import java.util.HashMap;
import java.util.Map;

/**
 * resolve el-expression
 * <p>
 * <p>    public static void main(String[] args) {
 * <p>        String el = "#{2 + 1}";
 * <p>        Map<String, Object> params = new HashMap<>();
 * <p>        params.put("roleId", "3");
 * <p>        System.out.println(getValue(el ,String.class, params));
 * <p>    }
 *
 * @author Mr.css
 * @version 2020-11-26 10:42
 */
public class EL {
    private EL() {
    }

    /**
     * el-expression
     *
     * @param el     the raw expression string to parse
     * @param target the class the caller would like the result to be
     * @param key    variable to set
     * @param value  value to be placed in the variable
     * @param <T>    return Class
     * @return the evaluation result
     */
    public static <T> T getValue(String el, Class<T> target, String key, @Nullable Object value) {
        ExpressionParser parser = new SpelExpressionParser();
        EvaluationContext context = new StandardEvaluationContext();
        context.setVariable(key, value);
        Expression expression = parser.parseExpression(el, new TemplateParserContext());
        return expression.getValue(context, target);
    }

    /**
     * el-expression
     *
     * @param el     the raw expression string to parse
     * @param target the class the caller would like the result to be
     * @param params variable to set
     * @param <T>    return Class
     * @return the evaluation result
     */
    public static <T> T getValue(String el, Class<T> target, Map<String, Object> params) {
        ExpressionParser parser = new SpelExpressionParser();
        StandardEvaluationContext context = new StandardEvaluationContext();
        context.setVariables(params);
        Expression expression = parser.parseExpression(el, new TemplateParserContext());
        return expression.getValue(context, target);
    }
}
